package com.example.service.Impl;

import com.example.Constants.SystemConstants;
import com.example.domain.ResponseResult;
import com.example.domain.dto.ModAuthorityDto;
import com.example.domain.entity.Authority;
import com.example.domain.entity.Menu;
import com.example.domain.vo.IdNameVo;
import com.example.domain.vo.ModInitAuthorityVo;
import com.example.enums.AppHttpCodeEnum;
import com.example.handler.exception.SystemException;
import com.example.mapper.AuthorityMapper;
import com.example.mapper.AuthorityMapperMenuMapper;
import com.example.mapper.MenuMapper;
import com.example.mapper.UserMapper;
import com.example.service.AuthorityService;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.function.Function;
import java.util.stream.Collectors;

@Service
public class AuthorityServiceImpl implements AuthorityService {
    @Resource
    private AuthorityMapper authorityMapper;
    @Resource
    private AuthorityMapperMenuMapper authorityMapperMenuMapper;
    @Resource
    private MenuMapper menuMapper;
    @Resource
    private UserMapper userMapper;
    @Override
    public ResponseResult getAuthorityList() {
        List<IdNameVo> idNameVoList = authorityMapper.selectAll();
        HashMap<String, List> map = new HashMap<>();
        map.put("authorityList",idNameVoList);
        return ResponseResult.okResult(map);
    }

    @Override
    @Transactional
    public ResponseResult deleteAuthority(Map<String, Integer> map) {
        Integer id = map.get("id");
        //将表中是被删除的用户权限改为普通用户
        userMapper.updateAuthorityByDeleteAuthorityId(id);
        if (SystemConstants.ADMIN.equals(id)||SystemConstants.NORMAL_USER.equals(id)){
            throw  new SystemException(AppHttpCodeEnum.DELETE_ADMIN_ERROR);
        }
        int updateNum = authorityMapper.deleteAuthority(id);
        if (updateNum!=1){
            throw  new SystemException(AppHttpCodeEnum.DELETE_ERROR);
        }
        return ResponseResult.okResult();
    }

    @Override
    @Transactional
    public ResponseResult modInitAuthority(Map<String, Integer> map) {
        Integer id = map.get("id");
        if (SystemConstants.ADMIN.equals(id)){
            throw new SystemException(AppHttpCodeEnum.DELETE_ADMIN_ERROR);
        }
        //查询权限名称
        Authority authority = authorityMapper.selectAuthorityNameById(id);
        if (Objects.isNull(authority)){
            throw new SystemException(AppHttpCodeEnum.SELECT_ERROR);
        }
        //查询所有菜单权限字段perm，id
        List<Menu> menuList = menuMapper.selectAllAuthorityPerm();
        List<IdNameVo> idNameVoList = menuList.stream()
                .map(menu -> new IdNameVo(menu.getId(), menu.getPerm()))
                .collect(Collectors.toList());
        //查询当前用户所拥有的的权限字段列表 perms
        List<IdNameVo> list = menuMapper.selectAuthorityPerm(id);
        List<String> perms = list.stream()
                .map(idNameVo -> idNameVo.getName())
                .collect(Collectors.toList());
        //封装Vo
        ModInitAuthorityVo modInitAuthorityVo = new ModInitAuthorityVo(authority.getAuthorityname(), idNameVoList,perms);
        return ResponseResult.okResult(modInitAuthorityVo);
    }

    @Override
    @Transactional
    public ResponseResult modAuthority(ModAuthorityDto modAuthorityDto) {
        //检查是否为超级管理员
        if (SystemConstants.ADMIN.equals(modAuthorityDto.getId())){
            throw new SystemException(AppHttpCodeEnum.DELETE_ADMIN_ERROR);
        }
        //如果权限列表没有id为1的首页菜单，直接抛异常很危险
        if (!modAuthorityDto.getPermsIdList().contains(SystemConstants.HOME_ID)){
            throw new SystemException(AppHttpCodeEnum.DELETE_ADMIN_ERROR);
        }
        //通过传入的名称检查修改的id是否等于传入的id(未删除状态)
        String id =authorityMapper.exitAuthorityId(modAuthorityDto.getName());
        if (!modAuthorityDto.getId().toString().equals(id)&&StringUtils.hasText(id)){
            throw new SystemException(AppHttpCodeEnum.NAME_ERROR);
        }
        //修改权限名称
        int updateNum = authorityMapper.updateAuthorityNameById(modAuthorityDto.getId(),modAuthorityDto.getName());
        if (updateNum==0){
            throw new SystemException(AppHttpCodeEnum.SYSTEM_ERROR);
        }
        //删除原有对应关系
//        int delNum = authorityMapperMenuMapper.deleteByAuthorityId(modAuthorityDto.getId());
        authorityMapperMenuMapper.deleteByAuthorityId(modAuthorityDto.getId());
        //修改权限与菜单列表对应表进行覆盖
        int insertNum = authorityMapperMenuMapper.insertByBatch(modAuthorityDto.getId(),modAuthorityDto.getPermsIdList());
        return ResponseResult.okResult();
    }

    @Override
    public ResponseResult addInitAuthority() {
        //查询所有权限已经对应id
        List<Menu> menuList = menuMapper.selectAllAuthorityPerm();
        List<IdNameVo> idNameVoList = menuList.stream()
                .map(menu -> new IdNameVo(menu.getId(), menu.getPerm()))
                .collect(Collectors.toList());
        HashMap<String, List<IdNameVo>> map = new HashMap<>();
        map.put("permsList",idNameVoList);
        return ResponseResult.okResult(map);
    }

    @Override
    @Transactional
    public ResponseResult addAuthority(ModAuthorityDto modAuthorityDto) {
        //通过传入的名称检查新增名称有无对应id(未删除状态)
        String id =authorityMapper.exitAuthorityId(modAuthorityDto.getName());
        if (StringUtils.hasText(id)){
            throw new SystemException(AppHttpCodeEnum.NAME_ERROR);
        }
        //新增权限获得其id
        authorityMapper.insertAuthority(modAuthorityDto);
        //增加权限与菜单列表对应表
        int insertNum = authorityMapperMenuMapper.insertByBatch(modAuthorityDto.getId(),modAuthorityDto.getPermsIdList());
        return ResponseResult.okResult();
    }
}
